package org.xurui.bsj.protocol.command.impl;

import lombok.extern.slf4j.Slf4j;
import org.jetlinks.core.message.CommonDeviceMessage;
import org.jetlinks.core.message.DeviceMessage;
import org.jetlinks.core.message.codec.EncodedMessage;
import org.jetlinks.core.message.codec.FromDeviceMessageContext;
import org.jetlinks.core.message.function.FunctionInvokeMessage;
import org.jetlinks.core.message.function.FunctionInvokeMessageReply;
import org.jetlinks.core.message.function.FunctionParameter;
import org.springframework.util.StringUtils;
import org.xurui.bsj.protocol.cache.ConcurrentMapCache;
import org.xurui.bsj.protocol.command.CmdCodec;
import org.xurui.bsj.protocol.enums.CommandEnum;
import org.xurui.bsj.protocol.msg.BsjMessage;
import org.xurui.bsj.protocol.msg.BsjMessageBuilder;
import org.xurui.bsj.protocol.utils.ArrayUtils;
import org.xurui.bsj.protocol.utils.BinaryUtils;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 4.2.4.实时位置获取
 */
@Slf4j
public class CmdCodec_LOCATION_INFO_GET implements CmdCodec {
    @Override
    public boolean supportsCmd(String cmd) {
        return CommandEnum.LOCATION_INFO_GET.name().equals(cmd);
    }

    @Override
    public List<DeviceMessage> parsePayload(BsjMessage payload, FromDeviceMessageContext context) {
        //例子：[35380100360174,898600MFSSYYGXXXXXXP,201805082000001000,LOCATION_INFO_GET,2,20180528111820,40,0E121.411783N31.178125T20080121165030@460! 0!9231!2351!-30@wifi!AC:BC:32:78:A2-:5F!97#wifi1!AC:BC:32:78:A2:5F!-97#wifi1! AC:BC:32:78:A2:5F!-97#wifi1!AC:BC:32:78:A2:5F!-97#wifi1!AC:BC:32:78:A2:5F!-9 7#wifi1!AC:BC:32:78:A2:5F!-97#wifi1!AC:BC:32:78:A2:5F!-97#wifi1!AC:BC:32:78:A 2:5F!-97#wifi1!AC:BC:32:78:A2:5F!-97#wifi1!AC:BC:32:78:A2:5F!-97#wifi1!AC:BC: 32:78:A2:5F!-97#wifi1!AC:BC:32:78:A2:5F!-97]
        //例子2： [35380100360174,898600MFSSYYGXXXXXXP,201805082000001000,LOCATION_INFO_GET,2,20180528111820,40,1E0.00000N0.00000T20080121165030@460!0!923 1!2351@0]
        /**
         * 报文体格式： 少于30组传全部， 最多30组， 需排除移动WIFI。
         * 位置信息 460,0,9231,2351,-30 : LBS 基站数据,MCC 国家码,460 为中国,0:MNC,0为移动, 9231:LAC,十进制, 2351,CID, 十进制
         * 如 果 GPS 数 据 包 中 状 态 为 1, 或 者 经 纬 度 为 ” 0000.0000N00000.0000E”时,则取 LBS 数据
         * wifi!AC:BC:32:78:A2:5F!-97 : 一组WIFI信息，wifi为 SSID， AC:BC:32:78:A2:5F为MAC地址，-97为信号 强度，变量之间用“!”分隔开WIFI信息可以有多组， 每组之间用“#”分隔
         * 无位置信息是补0
         * 字段说明：   位置信息(遵循NEMA报文格式GPS上报位置信息，参 见附录A)
         */
        //设备回复
        FunctionInvokeMessageReply report = FunctionInvokeMessageReply.create();
        report.setDeviceId(payload.getHeader().getDeviceNo());
        report.setFunctionId(payload.getHeader().getCmd());
        Object messageIdObj = ConcurrentMapCache.getInstance().getAndRemove(payload.getHeader().getOrderNo());
        String messageId = messageIdObj==null?null:messageIdObj.toString();
        if(messageId==null){
            messageId = payload.getHeader().getOrderNo();
        }
        report.setMessageId(messageId);
        report.setTimestamp(System.currentTimeMillis());
        Map<String, Object> properties = new HashMap<>();
        String tempBody = payload.getTempBody();
        String[] tempBodyArr = tempBody.split("@");
        //properties.put("header", FastBeanCopier.copy(payload.getHeader(), HashMap::new));
        properties.put("header", payload.getHeader().toMap());
        /**
         * GPS 位置信息：遵循 NEMA 报文格式 GPS 上报 位置信息，参见附录 A；
         */
        if(!StringUtils.isEmpty(ArrayUtils.getStrByIndex(tempBodyArr,0))){
            Map map= BinaryUtils.getGps(tempBodyArr[0]);
            properties.put("gpsStatus",map.get("gpsStatus"));
            properties.put("lonBs",map.get("lonBs"));
            properties.put("longitude",map.get("longitude"));
            properties.put("latBs",map.get("latBs"));
            properties.put("latitude",map.get("latitude"));
            properties.put("timeBs",map.get("timeBs"));
            properties.put("time",map.get("time"));
        }

        /**
         *            460,0,9231,2351,-30: LBS 基站数据,MCC 国家码,460 为中国,0:MNC,0 为移动, 9231:LAC, 十进制, 2351,CID,十进制
         *            如果 GPS 数据包中状态为 1, 或者经纬度为” 0000.0000N00000.0000E”时,则取 LBS 数据
         */
        properties.put("LBS",ArrayUtils.getStrByIndex(tempBodyArr,1));
        /**
         * wifi!AC:BC:32:78:A2:5F!-97: 一组 WIFI 信 息，wifi 为 SSID，AC:BC:32:78:A2:5F 为 MAC 地址，-97 为信号强度，变量之间用“!”分隔开 WIFI 信 息可以有多组，每组之间用“#”分隔
         */
        properties.put("wifiArr",ArrayUtils.getStrByIndex(tempBodyArr,2));
        report.setOutput(properties);
        return genDeviceMessage(report);
    }

    @Override
    public EncodedMessage encodeMessage(CommonDeviceMessage message,String zzs) {
        //平台下发消息
        //例子：[35380100360174,898600MFSSYYGXXXXXXP,201805082000001000,LOCATION_INFO_GET,1,20180528111820,0]
        /**
         * 报文体格式： 空
         */
        if(message instanceof FunctionInvokeMessage) {
            FunctionInvokeMessage m = (FunctionInvokeMessage) message;
            List<FunctionParameter> params = m.getInputs();
            Map<String, Object> paramsMap = params.stream()
                .collect(Collectors.toMap(FunctionParameter::getName, FunctionParameter::getValue));

            StringBuffer sb = new StringBuffer();

            return BsjMessageBuilder.create().buildBsjFunctionInvoickMessage(m,sb.toString());
        }else{
            if (log.isDebugEnabled()) {
                log.debug("非FunctionInvokeMessage指令{}消息{}",CommandEnum.LOCATION_INFO_GET.name(),message);
            }
            return null;
        }

    }
}
